package cn.buk.qms.service;

import cn.buk.common.JsonResult;
import cn.buk.common.sc.CommonSearchCriteria;
import cn.buk.tms.dao.AttractionDao;
import cn.buk.tms.sc.SearchFlightOrderCriteria;
import cn.buk.tms.dto.AttractionInfoDto;
import cn.buk.tms.dto.AttractionPriceDto;
import cn.buk.tms.dto.response.TicketOrderResponseDto;
import cn.buk.tms.entity.misc.*;
import cn.buk.tms.util.ValidationUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.annotation.Secured;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * 景点内容相关的服务方法
 */
@Service
public class AttractionServiceImpl extends BaseAbstractService implements AttractionService {

  @Autowired
  private AttractionDao dao;

  @Override
  @Secured({RoleInfo.ROLE_ADMIN, RoleInfo.ROLE_DATA_ADMIN})
  public JsonResult saveAttractionInfo(final int userId, AttractionInfoDto dto) {
    try {
      ValidationUtils.validate(dto);
    } catch (RuntimeException ex) {
      return JsonResult.createJsonResult(-1, ex.getMessage());
    }

    try {
      AttractionInfo info = AttractionInfoDto.convertedBy(dto);
      int retCode = dao.saveAttractionInfo(userId, info);
      return JsonResult.createJsonResult(retCode);
    } catch (RuntimeException ex) {
      return JsonResult.createJsonResult(-100, ex.getMessage());
    }
  }

  @Override
  public AttractionInfoDto getAttractionInfoById(int enterpriseId, int id) {
    AttractionInfo info = dao.getAttractionInfoById(id);
    if (info == null || info.getEnterpriseId() != enterpriseId) {
      return null;
    }

    return AttractionInfoDto.createdBy(info);
  }

  @Override
  public List<AttractionInfoDto> searchAttractions(int userId, CommonSearchCriteria sc) {
    List<AttractionInfo> infos = dao.searchAttractions(userId, sc);

    List<AttractionInfoDto> dtos = new ArrayList<>();
    for(AttractionInfo info: infos) {
      AttractionInfoDto dto = AttractionInfoDto.createdBy(info);
      dtos.add(dto);
    }

    return dtos;
  }

  @Override
  public JsonResult saveAttractionPrice(int userId, int attractionId, Date startDate, Date endDate, int price, String remark) {
    //校验日期
    if (startDate == null || endDate == null) {
      return JsonResult.createJsonResult(-1, "开始日期、截至日期不能为空.");
    }

    if (startDate.getTime() > endDate.getTime()) {
      return JsonResult.createJsonResult(-1, "开始日期不能大于截至日期.");
    }

    if (price < 1) {
      return JsonResult.createJsonResult(-2, "价格不对");
    }

    try {
      int retCode = dao.saveAttractionPrice(userId, attractionId, startDate, endDate, price, remark);
      return JsonResult.createJsonResult(retCode);
    } catch (RuntimeException ex) {
      return JsonResult.createJsonResult(-100, ex.getMessage());
    }
  }

  @Override
  public List<AttractionPriceDto> searchAttractionPrice(int userId, int attractionId, CommonSearchCriteria sc) {
    List<AttractionPrice> prices = dao.searchAttractionPrices(userId, attractionId, sc);

    List<AttractionPriceDto> dtos = new ArrayList<>();
    for(AttractionPrice price: prices) {
      AttractionPriceDto priceDto = new AttractionPriceDto();
      BeanUtils.copyProperties(price, priceDto);

      dtos.add(priceDto);
    }

    return dtos;
  }

  @Override
  public JsonResult deleteAttractionPrice(int userId, int attractionId, int priceId) {
    int retCode = dao.deleteAttractionPrice(userId, attractionId, priceId);
    return JsonResult.createJsonResult(retCode);
  }

  @Override
  public List<TicketOrderResponseDto> searchTicketOrders(final int userId, SearchFlightOrderCriteria sc) {
    final int enterpriseId = getEnterpriseIdByUserId(userId);

    List<TicketOrder> list = dao.searchTicketOrders(enterpriseId, sc);

    List<TicketOrderResponseDto> dtos = new ArrayList<>();

    for(TicketOrder info : list) {
      dtos.add(TicketOrderResponseDto.createdBy(info));
    }

    return dtos;
  }

  @Override
  public TicketOrderResponseDto getTicketOrder(int userId, int orderId) {
    TicketOrder ticketOrder = dao.getTicketOrderById(orderId);
    if (ticketOrder == null) {
      return null;
    } else {
      return TicketOrderResponseDto.createdBy(ticketOrder);
    }
  }

  @Override
  public List<OperationLog> searchTicketOrderHistory(final int userId, int orderId) {
    final int enterpriseId = getEnterpriseIdByUserId(userId);
    return dao.searchTicketOrderHistory(enterpriseId, orderId);
  }

  @Override
  @Secured({RoleInfo.ROLE_ADMIN, RoleInfo.ROLE_OPERATOR, RoleInfo.ROLE_SUPERVISOR})
  public JsonResult cancelTicketOrder(int userId, int orderId, String remark) {
    try {
      final int enterpriseId = getEnterpriseIdByUserId(userId);
      final String username = getUsernameByUserId(userId);

      int retCode = dao.cancelTicketOrder(enterpriseId, username, orderId, remark);
      return JsonResult.createJsonResult(retCode);
    } catch (Exception ex) {
      ex.printStackTrace();
      return JsonResult.createJsonResult(-100, ex.getMessage());
    }
  }

  @Override
  @Secured({RoleInfo.ROLE_ADMIN, RoleInfo.ROLE_SUPERVISOR, RoleInfo.ROLE_OPERATOR, RoleInfo.ROLE_TICKETER})
  public JsonResult processTicketOrder(int userId, int orderId, String remark) {
    final int enterpriseId = getEnterpriseIdByUserId(userId);
    final String username = getUsernameByUserId(userId);
    try {
      int retCode = dao.processTicketOrder(enterpriseId, username, orderId);
      return JsonResult.createJsonResult(retCode);
    } catch (RuntimeException ex) {
      return JsonResult.createJsonResult(-100, ex.getMessage());
    }
  }

  @Override
  @Secured({RoleInfo.ROLE_ADMIN, RoleInfo.ROLE_SUPERVISOR, RoleInfo.ROLE_OPERATOR, RoleInfo.ROLE_TICKETER})
  public JsonResult finishTicketOrder(int userId, int orderId, String remark) {
    final int enterpriseId = getEnterpriseIdByUserId(userId);
    final String username = getUsernameByUserId(userId);
    try {
      int retCode = dao.finishTicketOrder(enterpriseId, username, orderId, remark);
      //TODO 完成，自动导入账单
      return JsonResult.createJsonResult(retCode);
    } catch (RuntimeException ex) {
      return JsonResult.createJsonResult(-100, ex.getMessage());
    }
  }
}
